use common::error::{with_context, SysError};
use common::file_system::write_to_file;
use common::model::{EntryInfo, NpmModuleInfo, ProjectDirInfo, VueBlock};
use common::util::vue3::init_import;
use std::fs;
use std::path::Path;

pub fn setup_code(project_dir: &Path) -> Result<(), Box<dyn std::error::Error>> {
    let project_dir_info = ProjectDirInfo::new(project_dir);
    let npm_module_info = &NpmModuleInfo::new_for_dev(project_dir);
    init_import(&project_dir_info, npm_module_info)?;
    init_template(
        &project_dir_info,
        &npm_module_info
            .try_get_entry_info()
            .ok_or_else(|| SysError::msg("未发现entryInfo"))?,
    )?;
    Ok(())
}

fn init_template(
    project_dir_info: &ProjectDirInfo,
    entry_info: &EntryInfo,
) -> Result<(), Box<dyn std::error::Error>> {
    let vue_block = VueBlock::new(
        &fs::read_to_string(project_dir_info.app_vue())
            .map_err(|err| with_context(err, "读取app.vue失败"))?,
    );

    let template_content = format!("<{} />", entry_info.name);
    write_to_file(
        project_dir_info.app_vue(),
        vue_block
            .update_template_block(&template_content)?
            .get_source(),
    )?;
    Ok(())
}
